package com.raidpoints.client;

import java.util.ArrayList;
import java.util.HashMap;

import com.google.gwt.cell.client.AbstractCell;
import com.google.gwt.core.client.GWT;
import com.google.gwt.dom.client.Style.Unit;
import com.google.gwt.event.dom.client.ChangeEvent;
import com.google.gwt.event.dom.client.ChangeHandler;
import com.google.gwt.event.dom.client.ClickEvent;
import com.google.gwt.event.dom.client.ClickHandler;
import com.google.gwt.safehtml.shared.SafeHtmlBuilder;
import com.google.gwt.user.cellview.client.CellTable;
import com.google.gwt.user.cellview.client.Column;
import com.google.gwt.user.cellview.client.SimplePager;
import com.google.gwt.user.cellview.client.TextColumn;
import com.google.gwt.user.cellview.client.ColumnSortEvent.ListHandler;
import com.google.gwt.user.cellview.client.HasKeyboardSelectionPolicy.KeyboardSelectionPolicy;
import com.google.gwt.user.cellview.client.SimplePager.TextLocation;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.google.gwt.user.client.ui.Button;
import com.google.gwt.user.client.ui.Composite;
import com.google.gwt.user.client.ui.DockLayoutPanel;
import com.google.gwt.user.client.ui.HorizontalPanel;
import com.google.gwt.user.client.ui.ListBox;
import com.google.gwt.user.client.ui.ScrollPanel;
import com.google.gwt.view.client.ListDataProvider;
import com.google.gwt.view.client.SelectionChangeEvent;
import com.google.gwt.view.client.SingleSelectionModel;

public class CharacterPointsTable extends Composite{
	CellTable<pointsevent> eTable;
	ListDataProvider<pointsevent> dataProvider;
	ListHandler<pointsevent> sortHandler;
	SingleSelectionModel<pointsevent> selectionModel;
	RaidPoints rp;
	character mchar;
	SimplePager simplePager;
	Button recalcButton, modifyButton, accountButton;
	AsyncCallback<ArrayList<pointsevent>> pointsCallback;
	ListBox poolBox;
	int uid;
	int poolid;
	HashMap<String,Integer> poolmap;
	
	public CharacterPointsTable(RaidPoints mrp,character ch) {
		this(mrp,ch,-1);
	}
	
	public CharacterPointsTable(RaidPoints mrp,character ch, int mpoolid) {
		rp = mrp;
		mchar = ch;
		poolid = mpoolid;
		dataProvider = new ListDataProvider<pointsevent>();
		sortHandler = new ListHandler<pointsevent>(dataProvider.getList());
		selectionModel = new SingleSelectionModel<pointsevent>();
		poolmap = new HashMap<String,Integer>();
		
		DockLayoutPanel layoutPanel = new DockLayoutPanel(Unit.EM);
		initWidget(layoutPanel);
		
		eTable = new CellTable<pointsevent>();
		eTable.setPageSize(50);
		eTable.setSize("100%", "100%");
		eTable.setKeyboardSelectionPolicy(KeyboardSelectionPolicy.ENABLED);
		ScrollPanel scrollpan = new ScrollPanel();
		scrollpan.add(eTable);
		
		dataProvider.addDataDisplay(eTable);
		eTable.addColumnSortHandler(sortHandler);
		eTable.setSelectionModel(selectionModel);
		
		SimplePager.Resources pagerResources = GWT.create(SimplePager.Resources.class);
		simplePager = new SimplePager(TextLocation.CENTER,pagerResources,false,0,true);
		simplePager.setDisplay(eTable);
		
		HorizontalPanel hpan = new HorizontalPanel();
		
		poolBox = new ListBox();
		poolBox.setWidth("200px");
		hpan.add(poolBox);
		
		hpan.add(simplePager);
		
		final AsyncCallback<String> nameCallback = new AsyncCallback<String>(){

			@Override
			public void onFailure(Throwable caught) {
				// TODO Auto-generated method stub
				
			}

			@Override
			public void onSuccess(String result) {
				if(result != null){
					rp.ViewAccount(mchar.cid, result);
				}
			}
			
		};
		

		
		accountButton = new Button("View Account");
		accountButton.setVisible(false);
		accountButton.addClickHandler(new ClickHandler(){
			@Override
			public void onClick(ClickEvent event) {
				rp.rpsvc.AccountName(mchar.cid, nameCallback);
			}
		});
		hpan.add(accountButton);
		
		recalcButton = new Button("Recalc Points");
		recalcButton.setVisible(false);
		recalcButton.addClickHandler(new ClickHandler(){
			@Override
			public void onClick(ClickEvent event) {
				rp.rpsvc.RecalcPointsA(mchar.cid, poolmap.get(poolBox.getItemText(poolBox.getSelectedIndex())),poolBox.getItemText(poolBox.getSelectedIndex()),pointsCallback);
			}
		});
		
		hpan.add(recalcButton);
		
		modifyButton = new Button("Modify Char");
		modifyButton.setVisible(false);
		modifyButton.addClickHandler(new ClickHandler(){
			@Override
			public void onClick(ClickEvent event) {
				if(mchar.prole.equals("")){
					AsyncCallback<character> ccallback = new AsyncCallback<character>(){

						@Override
						public void onFailure(Throwable caught) {
							// TODO Auto-generated method stub
							
						}

						@Override
						public void onSuccess(character result) {
							AddCharacterBox ac = new AddCharacterBox(null,result,rp);
							ac.center(); ac.show();							
						}
						
					};
					rp.rpsvc.GetFullChar(mchar.cid, ccallback);
				}
				else{
				AddCharacterBox ac = new AddCharacterBox(null,mchar,rp);
				ac.center(); ac.show();
				}
			}
		});
		
		hpan.add(modifyButton);
		
		
		
		layoutPanel.addNorth(hpan, 3);
		layoutPanel.add(scrollpan);
		
//		while(rs.next()){
//			pointsevent tpe = new pointsevent();
//			tpe.charname = charname;
//			tpe.name = rs.getString("pointsevent.name");
//			tpe.change = rs.getDouble("pointsevent.change");
//			tpe.changetype = rs.getString("pointsevent.changetype");
//			if(tpe.changetype != null && tpe.changetype.equals("cinsert")) continue;
//			tpe.ts = rs.getTimestamp("events.starttime");
//			tpe.eid = rs.getInt("pointsevent.event_id");
//			tpe.pid = rs.getInt("pointsevent.id");
//			tpe.event = rs.getString("destinations.name") + " " + tpe.ts.toString().split(" ")[0];
//			pel.add(tpe);
//		}
		
		TextColumn<pointsevent> dateCol = new TextColumn<pointsevent>(){
			@Override
			public String getValue(pointsevent object) {
				return object.ts.getDate();
			}
			
		};
		eTable.addColumn(dateCol,"Date");
		
		TextColumn<pointsevent> destCol = new TextColumn<pointsevent>(){
			@Override
			public String getValue(pointsevent object) {
				return object.event;
			}
			
		};
		eTable.addColumn(destCol,"Dest");
		
//		TextColumn<pointsevent> lootCol = new TextColumn<pointsevent>(){
//			@Override
//			public String getValue(pointsevent object) {
//				return object.name;
//			}
//			
//		};
//		eTable.addColumn(lootCol,"Loot");
		
		Column<pointsevent,pointsevent> lootCol = new Column<pointsevent,pointsevent>(new LootCell()){

			@Override
			public pointsevent getValue(pointsevent object) {
				return object;
			}
			
		};
		eTable.addColumn(lootCol,"Loot");
		
		TextColumn<pointsevent> ttypeCol = new TextColumn<pointsevent>(){
			@Override
			public String getValue(pointsevent object) {
				return object.changetype;
			}
			
		};
		eTable.addColumn(ttypeCol,"Transaction");
		
		TextColumn<pointsevent> changeCol = new TextColumn<pointsevent>(){
			@Override
			public String getValue(pointsevent object) {
				return Double.toString(object.change);
			}
			
		};
		eTable.addColumn(changeCol,"Change");
		
		TextColumn<pointsevent> pointsCol = new TextColumn<pointsevent>(){
			@Override
			public String getValue(pointsevent object) {
				return Double.toString(object.currp);
			}
			
		};
		eTable.addColumn(pointsCol,"Points");
		
		final AsyncCallback<event> eventCallback = new AsyncCallback<event>(){

			@Override
			public void onFailure(Throwable caught) {
				// TODO Auto-generated method stub
				
			}

			@Override
			public void onSuccess(event result) {
				if(result != null) rp.ViewPoints(result);				
			}
			
		};
				
		selectionModel.addSelectionChangeHandler(new SelectionChangeEvent.Handler(){
			public void onSelectionChange(SelectionChangeEvent event) {
				pointsevent selected = selectionModel.getSelectedObject();
				if(selected != null){
					rp.rpsvc.GetEvent(selected.eid, eventCallback);
					selectionModel.setSelected(selected,false);
				}	
				
			}	
		});
		
		pointsCallback = new AsyncCallback<ArrayList<pointsevent>>(){

			@Override
			public void onFailure(Throwable caught) {
				// TODO Auto-generated method stub
				
			}

			@Override
			public void onSuccess(ArrayList<pointsevent> result) {
				dataProvider.getList().clear();
				dataProvider.getList().addAll(result);
				
				eTable.setRowCount(result.size());
				simplePager.firstPage();
			}
			
		};
		
		AsyncCallback<ArrayList<String>> poolCallback = new AsyncCallback<ArrayList<String>>(){

			@Override
			public void onFailure(Throwable caught) {
				// TODO Auto-generated method stub
				
			}

			@Override
			public void onSuccess(ArrayList<String> result) {
				poolmap.clear();
				int tbs = 0;
				int cc = 0;
				for(String s : result){
					String[] split = s.split(":;:");
					poolBox.addItem(split[0]);
					int pid = Integer.parseInt(split[1]);
					poolmap.put(split[0], pid);
					if(pid == poolid) tbs = cc;
					cc++;
				}
				poolBox.setSelectedIndex(tbs);
				UpdatePoints();
			}
			
		};
		
		poolBox.addChangeHandler(new ChangeHandler(){
			@Override
			public void onChange(ChangeEvent event) {
				UpdatePoints();				
			}
		});
		
		
		HandleAuthChange(rp.auth);
		rp.rpsvc.GetPools(mchar.gid,mchar.cid,poolCallback);
		//UpdatePoints();
	}
	
	public void UpdatePoints(){
		if(poolBox.getItemCount() == 0) return;		
		rp.rpsvc.GetCharHistory(mchar.cid,poolBox.getItemText(poolBox.getSelectedIndex()),pointsCallback);
	}
	
	public void HandleAuthChange(RaidPoints.AuthType atype){
		switch(atype){
		case admin:
			recalcButton.setVisible(true);
			modifyButton.setVisible(true);
			accountButton.setVisible(true);
			break;
		case cl:
			accountButton.setVisible(true);
			recalcButton.setVisible(false);
			modifyButton.setVisible(false);
			break;
		case user:
			accountButton.setVisible(true);
			recalcButton.setVisible(false);
			modifyButton.setVisible(false);
			break;
		default:
			accountButton.setVisible(false);
			recalcButton.setVisible(false);
			modifyButton.setVisible(false);
			break;
		}
		
	}
	
	public class LootCell extends AbstractCell<pointsevent>{

		@Override
		public void render(com.google.gwt.cell.client.Cell.Context context, pointsevent value, SafeHtmlBuilder sb) {
			if(value == null) return;
			if(value.name == null) return;
			String ln = value.name;
			if(!value.wowid.equals("")){
				if(value.gid == 1) ln = "<a href=\"#\" rel=\"item=" + value.wowid + "\">" + value.name + "</a>";
				else if(value.gid == 5) ln = "<a href=\"http://rift.magelo.com/en/item/" + value.wowid + "\">" + value.name + "</a>";		
			}
			sb.appendHtmlConstant(ln);	
		}
	}

}
